package io.gitee.guoguoleo.utils;

import cn.hutool.core.util.ArrayUtil;
import cn.hutool.json.JSONUtil;
import lombok.extern.slf4j.Slf4j;
import net.sf.jsqlparser.parser.CCJSqlParserUtil;
import org.apache.commons.lang3.StringUtils;
import org.springframework.dao.EmptyResultDataAccessException;
import org.springframework.dao.IncorrectResultSizeDataAccessException;
import org.springframework.jdbc.core.JdbcTemplate;

import java.util.List;
import java.util.Map;

@Slf4j
public class JdbcUtil {

    /**
     * 查询单条数据
     *
     * @param clazz        实体类
     * @param jdbcTemplate JdbcTemplate
     * @param sql          sql语句
     * @return 对象
     */
    public static <T> T get(Class<T> clazz, JdbcTemplate jdbcTemplate, String sql) {
        log.info("【one】查询语句:{}", JSONUtil.toJsonStr(sql));

        try {
            if (StringUtils.isBlank(sql)) {
                throw new RuntimeException("sql不能为空");
            }
            CCJSqlParserUtil.parse(sql);
        } catch (Exception e) {
            throw new RuntimeException("sql语句不合法", e);
        }
        try {
            Map<String, Object> resultMap = jdbcTemplate.queryForMap(sql);
            log.info("【one】查询结果:{}", JSONUtil.toJsonStr(resultMap));
            return EntityUtil.coverToEntity(resultMap, clazz);
        } catch (EmptyResultDataAccessException e) {
            log.info("【one】查询结果为空", e);
            return null;
        } catch (IncorrectResultSizeDataAccessException e) {
            log.info("【one】查询结果为数量不正确", e);
            throw new RuntimeException("需要使用list查询");
        }
    }

    /**
     * 查询批量数据
     *
     * @param clazz        实体类
     * @param jdbcTemplate JdbcTemplate
     * @param sql          sql语句
     * @return 对象
     */
    public static <T> List<T> list(Class<T> clazz, JdbcTemplate jdbcTemplate, String sql) {
        log.info("【list】查询语句:{}", sql);
        try {
            if (StringUtils.isBlank(sql)) {
                throw new RuntimeException("sql不能为空");
            }
            CCJSqlParserUtil.parse(sql);
        } catch (Exception e) {
            throw new RuntimeException("sql语句不合法", e);
        }
        try {
            List<Map<String, Object>> resultMapList = jdbcTemplate.queryForList(sql);
            log.info("【list】查询结果:{}", JSONUtil.toJsonStr(resultMapList));
            return EntityUtil.coverToEntityList(resultMapList, clazz);
        } catch (EmptyResultDataAccessException e) {
            log.info("【list】查询结果为空");
            return null;
        }
    }

    /**
     * 更新语句
     *
     * @param jdbcTemplate JdbcTemplate
     * @param sql          sql语句
     * @return 结果
     */
    public static boolean update(JdbcTemplate jdbcTemplate, String sql) {
        log.info("【update】执行update语句:{}", sql);
        try {
            if (StringUtils.isBlank(sql)) {
                throw new RuntimeException("sql不能为空");
            }
            CCJSqlParserUtil.parse(sql);
        } catch (Exception e) {
            throw new RuntimeException("sql语句不合法", e);
        }
        int result = jdbcTemplate.update(sql);
        log.info("【update】执行结果:{}", result);
        return result > 0;
//        return true;
    }

    /**
     * 批量更新语句
     *
     * @param jdbcTemplate jdbcTemplate
     * @param sqlArr       语句数组
     * @return 结果
     */
    public static boolean batchUpdate(JdbcTemplate jdbcTemplate, String... sqlArr) {
        log.info("【update】批量执行update语句:{}", JSONUtil.toJsonStr(sqlArr));
        try {
            if (ArrayUtil.isEmpty(sqlArr)) {
                throw new RuntimeException("sql不能为空");
            }
            for (String sql : sqlArr) {
                CCJSqlParserUtil.parse(sql);
            }
        } catch (Exception e) {
            throw new RuntimeException("sql语句不合法", e);
        }
        int[] result = jdbcTemplate.batchUpdate(sqlArr);
        log.info("【update】批量执行结果:{}", JSONUtil.toJsonStr(result));
        return result.length > 0;
//        return true;
    }


}
